﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace AspDotNet.Framework.MarkdownParser
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void richTextBoxOrgin_TextChanged(object sender, EventArgs e)
        {
            if (!string.IsNullOrWhiteSpace(richTextBoxOrgin.Text))
            {
                string result = richTextBoxOrgin.Text;

                GetMarkdownUrlMapping(result)
                    .ForEach(p =>
                    {
                        result = result.Replace(p.Key, $"`{p.Value}`");
                    });
                result = Regex.Replace(result, @"\*(\w+?)\*", "$1");
                result = Regex.Replace(result, @"(?<g1>\*+)(.+?)\k'g1'", "$1");

                richTextBoxParse.Text = result;
            }
        }

        /// <summary>
        /// 匹配 markdown URL
        /// 如:[IsConcurrencyToken](https://msdn.microsoft.com/library/gg679501(v=VS.103).aspx)
        /// </summary>
        /// <param name="orginStr"></param>
        /// <returns></returns>
        public List<KeyValuePair<string, string>> GetMarkdownUrlMapping(string orginStr)
        {
            var matches = Regex.Matches(orginStr, @"\[(.+?)\]\(.+?\)")
                .Cast<Match>()
                .Select(p => new KeyValuePair<string, string>(
                    new Func<string>(() =>
                    {
                        int endIndex = 0;
                        Stack<char> stack = new Stack<char>();
                        for (int i = p.Index; i < orginStr.Length; i++)
                        {
                            if (i == p.Index)
                            {
                                stack.Push(orginStr[i]);
                                continue;
                            }
                            if (orginStr[i] == ']')
                            {
                                if (stack.Count == 1 && stack.FirstOrDefault() == '[')
                                {
                                    stack.Pop();
                                    continue;
                                }
                            }
                            else if (orginStr[i] == '(')
                            {
                                stack.Push('(');
                                continue;
                            }
                            else if (orginStr[i] == ')')
                            {
                                stack.Pop();
                            }
                            if (stack.Count < 1)
                            {
                                endIndex = i;
                                break;
                            }
                        }
                        var result = orginStr.Substring(p.Index, endIndex - p.Index + 1);

                        return result;
                    })(),
                    p.Groups[1].Value))
                .ToList();
            return matches;
        }

        private void Form1_Activated(object sender, EventArgs e)
        {
            var data = Clipboard.GetText();
            richTextBoxOrgin.Text = data;
        }

        private void richTextBoxParse_TextChanged(object sender, EventArgs e)
        {
            if (!string.IsNullOrWhiteSpace(richTextBoxParse.Text))
            {
                Clipboard.Clear();
                Clipboard.SetText(richTextBoxParse.Text);
            }
        }
    }
}
